using System;

namespace Fadd.Commands
{
    /// <summary>
    /// Delegate used to handle commands.
    /// </summary>
    /// <param name="source"><see cref="ICommandDispatcher"/> that the command was invoked in.</param>
    /// <returns>true if command was handled.</returns>
    /// <param name="args">command arguments.</param>
    public delegate bool CommandHandler(object source, CommandEventArgs args);

    /// <summary>
    /// Event arguments for <see cref="CommandHandler"/>.
    /// </summary>
    public class CommandEventArgs : EventArgs
    {
        private readonly Command _command;
        private bool _cancelPropagation;
        private readonly bool _asynchronous;

        /// <summary>
        /// Initializes a new instance of the <see cref="CommandEventArgs"/> class.
        /// </summary>
        /// <param name="command">command that was invoked.</param>
        public CommandEventArgs(Command command)
        {
            if (command == null)
                throw new ArgumentNullException("command");

            _command = command;
        }

        /// <summary>
        /// Initializes a new instance of the <see cref="CommandEventArgs"/> class.
        /// </summary>
        /// <param name="command">command that was invoked.</param>
        /// <param name="isAsynchrounous">Command is being invoked asynchrounosly.</param>
        public CommandEventArgs(Command command, bool isAsynchrounous)
        {
            if (command == null)
                throw new ArgumentNullException("command");

            _command = command;
            _asynchronous = isAsynchrounous;
        }

        /// <summary>
        /// Command that was invoked.
        /// </summary>
        public Command Command
        {
            get { return _command; }
        }

        /// <summary>
        /// Abort the handled of this command.
        /// </summary>
        /// <remarks>
        /// The event <see cref="CommandManager.PropagationCancelled"/> can override this property.
        /// </remarks>
        public bool CancelPropagation
        {
            get { return _cancelPropagation; }
            set { _cancelPropagation = value; }
        }

        /// <summary>
        /// Command is being invoked asynchrounosly.
        /// </summary>
        public bool IsAsynchronous
        {
            get { return _asynchronous; }
        }
    }

}
